﻿#light

// 12.12.08 Matt Valerio

// Original discussion:
// http://groups.google.com/group/f-for-scientists-book-club/browse_thread/thread/6cb9b0efeb99ac04

let p0 = [| 0.7; 0.2; 0.4; 0.1 |];
let points = [ [| 0.0; 0.0; 0.0; 0.0 |];
               [| 1.0; 0.0; 0.0; 0.0 |];
               [| 0.0; 1.0; 0.0; 0.0 |];
               [| 0.0; 0.0; 1.0; 0.0 |];
               [| 0.0; 0.0; 0.0; 1.0 |];
               [| 1.0; 1.0; 0.0; 0.0 |];
               [| 0.0; 1.0; 1.0; 0.0 |];
               [| 0.0; 0.0; 1.0; 1.0 |];
               [| 1.0; 0.0; 0.0; 1.0 |];
             ]
             
let distance xs ys =
  Seq.map2 (-) xs ys
  |> Seq.map (fun x -> x * x)
  |> Seq.sum
  |> sqrt
  
let shortest_distance (points : float array list) (p0 : float array) =
  points 
  |> Seq.map (distance p0)
  |> Seq.min
  
let closest_point (points : float array list) (p0 : float array) =
  points
  |> Seq.map (distance p0)
  |> Seq.zip points
  |> Seq.sort_by snd
  |> Seq.hd

let () =
  let result = closest_point points p0
  printfn "Closest point to p0=%A:" p0
  printfn " dist=%f, point=%A" (snd result) (fst result)
  
